#pragma once

class BigRedButtonNotifications {
public:

	virtual void BLidStateChange( bool lidOpen ) = 0;
	virtual void BButtonStateChange( bool buttonPressed ) = 0;

};

class BigRedButton {
public:

	BigRedButton( BigRedButtonNotifications* pOwner, int refreshRate = 20 );
	~BigRedButton( );

	bool Open( );
	bool Close( );

	inline int GetRefreshRate( void ) const {
		return refreshRate;
	}
	bool SetRefreshRate( int const newRefreshRate );

	bool IsOpen( void ) const {
		return ( nullptr != hReaderThread || nullptr != hWriterThread || INVALID_HANDLE_VALUE != hInputDevice || INVALID_HANDLE_VALUE != hOutputDevice );
	}

private:

	HANDLE hReaderThread;
	HANDLE hWriterThread;

	HANDLE hInputDevice;
	HANDLE hOutputDevice;

	HANDLE hTimer;
	HANDLE hShutdownEvent;

	BigRedButtonNotifications* pOwner;
	int refreshRate;

	bool LidOpen;
	bool ButtonPressed;

	HIDP_CAPS Capabilities;

	void _CleanUp( void );
	bool _CreateWaitableTimer( void );

	void _RaiseLidStateChange( bool lidOpen );
	void _RaiseButtonStateChange( bool buttonPressed );

	bool _StartReaderThread( void );
	bool _StartWriterThread( void );

	static unsigned __stdcall _ReaderThunk( void* pv );
	static unsigned __stdcall _WriterThunk( void* pv );

	void _ReaderThread( void );
	void _WriterThread( void );

};
